/*
 * yangchengtong.h
 *
 *  Created on: 2018-10-9
 *      Author: ltp
 */

#ifndef YANGCHENGTONG_H_
#define YANGCHENGTONG_H_

#include "libcard.h"

#define   DEDUCTION_FEE  //是否扣费的宏定义

//响应报文状态码
enum MsgStatusCode{
	MOC_ERROR_NORMAL = 0X00,  //操作正常
	MOC_ERROR_CARD_OVERLIMIT = 0x96,  //钱包余额超出上限
	MOC_ERROR_CARD_OWEPAY = 0x95,  //钱包余额不足
	MOC_ERROR_CARD_OUTOF_DATE = 0x91,	//卡片超出有效期或超出卡离线有效期
	MOC_ERROR_CARDTIMEOUT_MONTH  = 0xF,	//离线月份参数非法
	MOC_ERROR_NO_RECORD = 0xC2,	//根据输入的条件，无对应的记录
	MOC_ERROR_CARD_SETBLACKLIST = 0xC5,		//卡片置黑名单报错
	MOC_ERROR_SAM_EMPTY = 0x60,		//没有安装 SAM 卡
	MOC_ERROR_SAM_INIT = 0x61,		//SAM 卡初始化错误或未初始化
	MOC_ERROR_SAM_PIN = 0x62,		//SAM 卡检验 PIN 错误
	MOC_ERROR_SAM_TYPE = 0x63,		//SAM 卡类型与交易类型不匹配
	MOC_ERROR_SAM_SELECT = 0x64,		//SAM 卡选择文件错误
	MOC_ERROR_SAM_READ = 0x65,			//SAM 卡读错误
	MOC_ERROR_SAM_WRITE = 0x66,		//SAM 卡写错误
	MOC_ERROR_SAM_AUTH = 0x67,		//SAM 卡认证错误
	MOC_ERROR_SAM_CHALLENGE = 0x68,	//SAM 卡随机数错误
	MOC_ERROR_SAM_DES = 0x69,		//SAM 卡 DES 计算错误
	MOC_ERROR_SAM_CREATE_KEY = 0x6A,	//SAM 卡生成钱包密钥错误
	MOC_ERROR_PKI_RSA = 0x71,		//PKI 卡 RSA 计算错误
	MOC_ERROR_PKI_DES = 0x72,		//PKI 卡 DES 计算错误
	MOC_ERROR_SAM_APDU = 0x7E,		//SAM 卡执行 APDU 命令错误
	MOC_ERROR_SAM_TIMEOUT = 0x7F,		//SAM 卡操作超时
	MOC_ERROR_CARD_NOTAG = 0x80,		//没有卡
	MOC_ERROR_CARD_SELECT = 0x81,		//选择卡片错误
	MOC_ERROR_CARD_HALT = 0x82,		//停用卡片错误
	MOC_ERROR_CARD_AUTH = 0x83,		//认证卡片错误
	MOC_ERROR_CARD_READ = 0x84,		//卡片读操作错误
	MOC_ERROR_CARD_WRITE = 0x85,		//卡片写操作错误
	MOC_ERROR_CARD_PENDING = 0x86,		//卡片写操作中途中断
	MOC_ERROR_CARD_NORESP = 0x87,			//充值卡片无响应
	MOC_ERROR_CARD_UNKOWN = 0x90,		//不是本系统标准的卡片
	MOC_ERROR_CARD_CITY = 0x92,			//城市代码或应用代码错误
	MOC_ERROR_CARD_INVALID = 0x93,		//非法卡
	MOC_ERROR_CARD_NAMELIST = 0x94,		//黑名单卡
	MOC_ERROR_CARD_PURSE_UNUSED = 0x97,		//钱包未启用
	MOC_ERROR_CARD_PURSE_STOPPED = 0x98,		//钱包已停用
	MOC_ERROR_CARD_PURSE_FAIL = 0x99,		//钱包正本被破坏
	MOC_ERROR_CARD_PURSE_INUSE = 0x9A,		//钱包已停用
	MOC_ERROR_CARD_MUTEX_FAIL = 0x9F,		//公共信息区被破坏
	MOC_ERROR_CARD_TIMEOUT = 0xAF,		//卡片操作超时
	MOC_ERROR_TS_PENDING = 0xB0,			//交易操作中途中断
	MOC_ERROR_TS_FAIL = 0xB1,		//交易中断
	MOC_ERROR_TS_STEP = 0xB2,		//前一步指令未执行或执行失败
	MOC_ERROR_CARD_TS_TIMEOUT = 0xCF,		//交易操作超时
	MOC_ERROR_CARD_HOST_CTL = 0xD0,		//远程读写器执行错
	MOC_ERROR_MIFARE_INIT = 0xE0,		//MIFARE 硬件初始化错误
	MOC_ERROR_ICC_INIT = 0xE1,		//SAM 硬件初始化错误
	MOC_ERROR_INVALID_COMMAND = 0xE2,		//命令错误
	MOC_ERROR_INVALID_PARAM = 0xE3,		//参数错误
	MOC_ERROR_CHECKSUM = 0xE4,		//检验和错误
	MOC_ERROR_COMM_TIMEOUT = 0xE5,		//线路通讯超时
	MOC_ERROR_FLASH_WRITE = 0xE6,		//内部 FLASH 写错误
	PAC_ERROR_HEADER_INVALID = 0x30,		//报文头错
	PAC_ERROR_CARD_CHANGE = 0x31,		//卡片不一致
	PAC_ERROR_SYSSEQU = 0x32,		//流水号不一致
	PAC_ERROR__MAC = 0x33,		//MAC 错
	ERROR_COMMAND = 0x3F,		//不支持的命令
	MOC_ERROR_CARDNO_DIFFERENT = 0x1A	//物理卡号不一致
};



enum WalletType{
	WALLET_M1 = 0x01,//M1钱包
	WALLET_CPU = 0x02,//CPU钱包
};

/*羊城通终端到读卡器报文结构体： Header+Len+Command+Data+Checksum*/
struct Msg_Terminal_to_Card{
	unsigned char header;
	unsigned char dataLen;
	unsigned char frameLen;
	unsigned char command;
	unsigned char data[128];
	unsigned char cs;
};

/*羊城通读卡器到终端报文结构体： Header+Len+Command+Status+Data+Checksum*/
struct Msg_Card_to_Terminal{
	unsigned char header;
	unsigned char dataLen;
	unsigned char command;
	unsigned char status;
	unsigned char data[255];
	unsigned char cs;
};

/*拓展应用复合记录*/
struct yct_cpu_card_develop_app_record{
	unsigned char operator_code[2];//运营商编码
	unsigned char record_ver;//记录版本号
	unsigned char record_flag;//记录标识
	unsigned char record_protocol_len;//记录协议长度
	unsigned char devNum[8];//充电桩设备编号
	unsigned char devState;//设备状态  01：正在充电  02：完成结算
	unsigned char trade_serial_num[4];//交易流水号
	unsigned char trade_time[7];//交易时间
	unsigned char PSAM_Num[6];//扣费模块编号
	int RFU;
	int crc16;//校验码
};

/*羊城通卡片信息由本动态库寻卡获得，供主控或UI使用*/
struct yct_card_info{
	unsigned char wallet_type;//钱包类别 0x01： 使用 M1 钱包  0x02： 使用 CPU 钱包
	unsigned char cardNum[8];//物理卡号
	unsigned char logicNum[8];//逻辑卡号
	unsigned char money_low_limit;//金额下限
	unsigned char area_code;
	unsigned char area_card_num[8];
	unsigned char area_card_valid_date[4];
	unsigned char SAK;
	unsigned char area_sub_code;//区域子码
	unsigned char ATQA[2];
	int balance;//余额 单位：分
	int card_count;//卡计数器
	int card_type;//卡类型
	int money_up_limit;//金额上限
	int deposit;//卡押金
	int area_card_type;//区域卡类型
	int actual_balance;//实际显示余额 余额-金额下限，可显示为负数   单位：分
	int over_balance;//可透支余额 单位：分
	struct yct_cpu_card_develop_app_record app_record;
};

/*羊城通消费信息 终端-->读卡器*/
struct yct_consume_to_card{
	int original_trade_money;//原交易金额 (高字节在前，以分为单位) 即预扣款30.5元=3050分
	int actual_trade_money;//实际交易金额。以分为单位， 1.36元==136分
	unsigned char terminal_trade_date[4];//BCD 20101210 <--->2010-12-10
	unsigned char terminal_trade_time[3];//BCD 204709   <----->20:47:09
	unsigned char pend_offline_flag;//卡离线有效期启用BCD 00（不判断离线时间） 或 01（ 需要判断离线时间）
	unsigned char offline_valid_date;//卡离线有效期启用BCD   以月为单位  如：学生卡离线时间 4 个月则填 0x04
	struct yct_cpu_card_develop_app_record record;
};

/*羊城通消费信息 读卡器-->终端*/
union yct_consume_from_card{
	struct{
		unsigned char terminal_trade_serial_num[4];//终端交易流水号
		unsigned char logic_cardNum[8];//逻辑卡号
		unsigned char cardNum[8];//物理卡号
		unsigned char last_trade_devNum[4];//上次交易设备编号
		unsigned char last_trade_time[7];//上次交易日期时间  默认值为本次交易日期时间
		unsigned char SAM_logiv_num[4];//本次交易设备编号  SAM卡逻辑卡号
		unsigned char cur_trade_time[7];//本次交易日期时间
		int trade_money;//交易金额
		int balance;//本次余额
		int ticket_price;//票价
		int trade_type;//交易类型
		int ticket_count;//票卡交易计数
		unsigned char add_door_mounth[2];//累计门槛月份
		unsigned char bus_door_count;//公交门槛计数
		unsigned char subway_door_count;//地铁门槛计数
		unsigned char joint_multiplication;//联乘门槛计数
		unsigned char trade_door_devNum[4];//本次交易入口设备编号  SAM卡逻辑卡号
		unsigned char trade_door_time[7];//本次交易入口日期时间
		unsigned char trade_ident_code[4];//交易认证码
	}m1;
	struct{
		unsigned char trade_devNum[6];//本次交易设备编号
		unsigned char terminal_trade_serial_num[4];//终端交易流水号
		unsigned char cur_trade_time[7];//本次交易日期时间
		unsigned char logic_cardNum[8];//逻辑卡号
		unsigned char cardNum[8];//物理卡号
		int trade_money;//交易金额
		int ticket_price;//票价
		int balance;//本次余额
		int trade_type;//交易类型
		int add_trade_type;//附加交易类型
		int ticket_recharge_count;//票卡充值交易计数
		int ticket_consume_count;//票卡消费交易计数
		unsigned char add_door_mounth[2];//累计门槛月份
		unsigned char bus_door_count;//公交门槛计数
		unsigned char subway_door_count;//地铁门槛计数
		unsigned char joint_multiplication;//联乘门槛计数
		unsigned char trade_door_devNum[6];//本次交易入口设备编号
		unsigned char trade_door_time[7];//本次交易入口日期时间
		unsigned char last_trade_devNum[6];//上次交易设备编号
		unsigned char last_trade_time[4];//上次交易日期时间 MMDDHHMM (24小时制
		unsigned char area_code;//区域代码
		int area_card_type;//区域卡类型
		unsigned char area_sub_code;//区域子码
		unsigned char trade_ident_code[4];//交易认证码
	}cpu;
};




struct yct_card{
	struct yct_card_info card_info; //卡片信息  由动态库读卡获取，供UI和主控使用
	union yct_consume_from_card consume_info;//消费后的卡片信息，供UI和主控使用
	int card_state;//读卡状态
	unsigned char app_flag;//应用标识 00：普通消费 01：复合消费
	unsigned char PSAM[6];//PSAM 卡号
	unsigned char devNum[8];//设备号

	struct yct_consume_to_card  consume_precondition;//消费预处理 由UI或主控填充
	yct_incomplete_trade incomplete_trade;//未完整交易 由UI或主控填充
};

//羊城通 预处理 0:成功  主要做启动充电的预扣费用
int protocol_yct_consume_precondition(struct yct_card* pCard,  char recordFlag, char devState );

//羊城通 未完整交易处理 0成功 主要做结算扣费   TAC是4个字节的数组
int protocol_yct_incomplete_consume_deal(struct yct_card* pCard, unsigned char *TAC, int tac_len);

//羊城通 消费  consume_flag: 0:普通消费  1:复合消费 成功返回0
int protocol_yct_consume();

//羊城通 捕捉黑名单卡
int protocol_yct_catch_blacklist_card(void);









#endif /* YANGCHENGTONG_H_ */
